home *** CD-ROM | disk | FTP | other *** search
/ Collection of Tools & Utilities / Collection of Tools and Utilities.iso / print / gs261sr1.zip / GSCHAR.C < prev    next >
C/C++ Source or Header  |  1993-05-27  |  25KB  |  787 lines

  1. /* Copyright (C) 1989, 1992, 1993 Aladdin Enterprises.  All rights reserved.
  2.  
  3. This file is part of Ghostscript.
  4.  
  5. Ghostscript is distributed in the hope that it will be useful, but
  6. WITHOUT ANY WARRANTY.  No author or distributor accepts responsibility
  7. to anyone for the consequences of using it or for whether it serves any
  8. particular purpose or works at all, unless he says so in writing.  Refer
  9. to the Ghostscript General Public License for full details.
  10.  
  11. Everyone is granted permission to copy, modify and redistribute
  12. Ghostscript, but only under the conditions described in the Ghostscript
  13. General Public License.  A copy of this license is supposed to have been
  14. given to you along with Ghostscript so you can know your rights and
  15. responsibilities.  It should be in a file named COPYING.  Among other
  16. things, the copyright notice and this notice must be preserved on all
  17. copies.  */
  18.  
  19. /* gschar.c */
  20. /* Character writing operators for Ghostscript library */
  21. #include "gx.h"
  22. #include "memory_.h"
  23. #include "string_.h"
  24. #include "gserrors.h"
  25. #include "gxfixed.h"            /* ditto */
  26. #include "gxarith.h"
  27. #include "gxmatrix.h"
  28. #include "gzstate.h"            /* must precede gzdevice */
  29. #include "gzdevice.h"            /* must precede gxchar */
  30. #include "gxdevmem.h"
  31. #include "gxchar.h"
  32. #include "gxcache.h"
  33. #include "gxfont.h"
  34. #include "gspath.h"
  35. #include "gzpath.h"
  36. #include "gzcolor.h"
  37.  
  38. /* Exported size of enumerator */
  39. const uint gs_show_enum_sizeof = sizeof(gs_show_enum);
  40.  
  41. /* Imported procedures */
  42. extern void gx_set_black(P1(gs_state *));
  43.  
  44. /* Forward declarations */
  45. private int continue_kshow(P1(gs_show_enum *));
  46. private int continue_show(P1(gs_show_enum *));
  47. private int continue_show_update(P1(gs_show_enum *));
  48. private int show_setup(P3(gs_show_enum *, gs_state *, const char *));
  49. private void show_cache_setup(P1(gs_show_enum *));
  50. private int show_state_setup(P1(gs_show_enum *));
  51. private int show_origin_setup(P4(gs_state *, fixed, fixed, int));
  52. private int stringwidth_setup(P3(gs_show_enum *, gs_state *, const char *));
  53.  
  54. /* Print the ctm if debugging */
  55. #define print_ctm(s,pgs)\
  56.   dprintf7("[p]%sctm=[%g %g %g %g %g %g]\n", s,\
  57.        pgs->ctm.xx, pgs->ctm.xy, pgs->ctm.yx, pgs->ctm.yy,\
  58.        pgs->ctm.tx, pgs->ctm.ty)
  59.  
  60. /* ------ String writing operators ------ */
  61.  
  62. /* Setup macros for show operators */
  63. #define setup_show_n()\
  64.   penum->size = size
  65. #define setup_a()\
  66.   penum->add = 1, penum->ax = ax, penum->ay = ay,\
  67.   penum->slow_show = 1
  68. #define setup_width()\
  69.   penum->wchr = chr, penum->wcx = cx, penum->wcy = cy,\
  70.   penum->slow_show = 1
  71.  
  72. /* show[_n] */
  73. int
  74. gs_show_n_init(register gs_show_enum *penum,
  75.    gs_state *pgs, const char *str, uint size)
  76. {    setup_show_n();
  77.     penum->slow_show = 0;
  78.     return show_setup(penum, pgs, str);
  79. }
  80. int
  81. gs_show_init(gs_show_enum *penum, gs_state *pgs, const char *str)
  82. {    return gs_show_n_init(penum, pgs, str, strlen(str));
  83. }
  84.  
  85. /* ashow[_n] */
  86. int
  87. gs_ashow_n_init(register gs_show_enum *penum,
  88.   gs_state *pgs, floatp ax, floatp ay, const char *str, uint size)
  89. {    int code;
  90.     setup_show_n();
  91.     code = show_setup(penum, pgs, str);
  92.     setup_a();
  93.     return code;
  94. }
  95. int
  96. gs_ashow_init(gs_show_enum *penum,
  97.   gs_state *pgs, floatp ax, floatp ay, const char *str)
  98. {    return gs_ashow_n_init(penum, pgs, ax, ay, str, strlen(str));
  99. }
  100.  
  101. /* widthshow[_n] */
  102. int
  103. gs_widthshow_n_init(register gs_show_enum *penum,
  104.   gs_state *pgs, floatp cx, floatp cy, gs_char chr, const char *str, uint size)
  105. {    int code;
  106.     setup_show_n();
  107.     code = show_setup(penum, pgs, str);
  108.     setup_width();
  109.     return code;
  110. }
  111. int
  112. gs_widthshow_init(gs_show_enum *penum,
  113.   gs_state *pgs, floatp cx, floatp cy, gs_char chr, const char *str)
  114. {    return gs_widthshow_n_init(penum, pgs, cx, cy, chr, str, strlen(str));
  115. }
  116.  
  117. /* awidthshow[_n] */
  118. int
  119. gs_awidthshow_n_init(register gs_show_enum *penum,
  120.   gs_state *pgs, floatp cx, floatp cy, gs_char chr, floatp ax, floatp ay,
  121.   const char *str, uint size)
  122. {    int code;
  123.     setup_show_n();
  124.     code = show_setup(penum, pgs, str);
  125.     setup_a();
  126.     setup_width();
  127.     return code;
  128. }
  129. int
  130. gs_awidthshow_init(gs_show_enum *penum,
  131.   gs_state *pgs, floatp cx, floatp cy, gs_char chr, floatp ax, floatp ay,
  132.   const char *str)
  133. {    return gs_awidthshow_n_init(penum, pgs, cx, cy, chr, ax, ay,
  134.                     str, strlen(str));
  135. }
  136.  
  137. /* kshow[_n] */
  138. int
  139. gs_kshow_n_init(register gs_show_enum *penum,
  140.   gs_state *pgs, const char *str, uint size)
  141. {    int code;
  142.     if ( pgs->font->FontType == ft_composite)
  143.         return_error(gs_error_invalidfont);
  144.     setup_show_n();
  145.     code = show_setup(penum, pgs, str);
  146.     penum->do_kern = penum->slow_show = 1;
  147.     return code;
  148. }
  149. int
  150. gs_kshow_init(gs_show_enum *penum, gs_state *pgs, const char *str)
  151. {    return gs_kshow_n_init(penum, pgs, str, strlen(str));
  152. }
  153.  
  154. /* xyshow[_n] */
  155. int
  156. gs_xyshow_n_init(register gs_show_enum *penum,
  157.    gs_state *pgs, const char *str, uint size)
  158. {    int code;
  159.     setup_show_n();
  160.     code = show_setup(penum, pgs, str);
  161.     penum->do_kern = -1;
  162.     penum->slow_show = 1;
  163.     return code;
  164. }
  165. int
  166. gs_xyshow_init(gs_show_enum *penum, gs_state *pgs, const char *str)
  167. {    return gs_xyshow_n_init(penum, pgs, str, strlen(str));
  168. }
  169.  
  170. /* glyphshow */
  171. private gs_proc_encode_char(gs_glyphshow_encode_char);
  172. int
  173. gs_glyphshow_init(gs_show_enum *penum, gs_state *pgs, gs_glyph glyph)
  174. {    int code;
  175.     if ( pgs->font->FontType == ft_composite)
  176.         return_error(gs_error_invalidfont);
  177.     penum->size = 1;
  178.     penum->slow_show = 0;
  179.     code = show_setup(penum, pgs, "\000");    /* arbitrary char */
  180.     penum->current_glyph = glyph;
  181.     penum->encode_char = gs_glyphshow_encode_char;
  182.     return code;
  183. }
  184. private gs_glyph
  185. gs_glyphshow_encode_char(gs_show_enum *penum, gs_font *pfont, gs_char *pchr)
  186. {    /* We just nil out the character, and return the pre-loaded glyph. */
  187.     *pchr = gs_no_char;
  188.     return penum->current_glyph;
  189. }
  190.  
  191. /* cshow[_n] */
  192. int
  193. gs_cshow_n_init(register gs_show_enum *penum,
  194.    gs_state *pgs, const char *str, uint size)
  195. {    int code;
  196.     setup_show_n();
  197.     code = show_setup(penum, pgs, str);
  198.     penum->do_kern = -1;
  199.     penum->stringwidth_flag = 1;
  200.     penum->slow_show = 1;
  201.     return code;
  202. }
  203. int
  204. gs_cshow_init(gs_show_enum *penum, gs_state *pgs, const char *str)
  205. {    return gs_cshow_n_init(penum, pgs, str, strlen(str));
  206. }
  207.  
  208. /* ------ Related operators ------ */
  209.  
  210. /* stringwidth[_n] */
  211. int
  212. gs_stringwidth_n_init(gs_show_enum *penum, gs_state *pgs, const char *str, uint size)
  213. {    setup_show_n();
  214.     return stringwidth_setup(penum, pgs, str);
  215. }
  216. int
  217. gs_stringwidth_init(gs_show_enum *penum, gs_state *pgs, const char *str)
  218. {    return gs_stringwidth_n_init(penum, pgs, str, strlen(str));
  219. }
  220.  
  221. /* Common code for stringwidth[_n] */
  222. private int
  223. stringwidth_setup(gs_show_enum *penum, gs_state *pgs, const char *str)
  224. {    int code = (penum->slow_show = 0, show_setup(penum, pgs, str));
  225.     if ( code < 0 ) return_error(code);
  226.     penum->stringwidth_flag = 1;
  227.     /* Do an extra gsave and suppress output */
  228.     if ( (code = gs_gsave(pgs)) < 0 ) return code;
  229.     penum->level = pgs->level;    /* for level check in show_update */
  230.     /* Set up a null device that forwards xfont requests properly. */
  231.     penum->dev_null = gs_null_device;
  232.     penum->dev_null.target = pgs->device->info;
  233.     pgs->device->info = (gx_device *)&penum->dev_null;
  234.     /* Establish an arbitrary current point. */
  235.     return gx_path_add_point(pgs->path, pgs->ctm.tx_fixed, pgs->ctm.ty_fixed);
  236. }
  237.  
  238. /* charpath[_n] */
  239. int
  240. gs_charpath_n_init(gs_show_enum *penum, gs_state *pgs,
  241.   const char *str, uint size, int bool)
  242. {    int code;
  243.     setup_show_n();
  244.     code = show_setup(penum, pgs, str);
  245.     penum->charpath_flag = (bool ? 2 : 1);
  246.     penum->can_cache = 0;
  247.     return code;
  248. }
  249. int
  250. gs_charpath_init(gs_show_enum *penum, gs_state *pgs,
  251.   const char *str, int bool)
  252. {    return gs_charpath_n_init(penum, pgs, str, strlen(str), bool);
  253. }
  254.  
  255. /* ------ Width/cache operators ------ */
  256.  
  257. private int set_cache_device(P6(gs_show_enum *, gs_state *,
  258.   floatp, floatp, floatp, floatp));
  259.  
  260. /* setcachedevice */
  261. int
  262. gs_setcachedevice(gs_show_enum *penum, gs_state *pgs,
  263.   floatp wx, floatp wy, floatp llx, floatp lly, floatp urx, floatp ury)
  264. {    int code = gs_setcharwidth(penum, pgs, wx, wy);    /* def